package net.toocruel.iqismart.web.handler;

import net.sf.json.JSONObject;
import net.toocruel.iqismart.security.core.support.Result;
import net.toocruel.iqismart.service.exception.AccessDeniedException;
import net.toocruel.iqismart.service.exception.BusinessException;
import net.toocruel.iqismart.service.exception.NotFoundException;
import net.toocruel.iqismart.web.exception.SessionInvalidException;
import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.validation.FieldError;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.servlet.mvc.support.RedirectAttributes;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * 全局异常处理类
 *
 * @Description
 *
 * @Auther sty
 * @createTime 2018/4/28 下午6:10
 */
@ControllerAdvice
public class GlobalExceptionHandler {

    private Logger logger = LoggerFactory.getLogger(getClass());

    /**
     * 系统异常
     * @param req
     * @param e
     * @return
     * @throws Exception
     */
    @ExceptionHandler(value = Exception.class)
    public String defaultErrorHandler(HttpServletRequest req, HttpServletResponse res, Exception e,RedirectAttributes redirectAttributes) throws Exception {

        String referer = req.getHeader("referer");
        String ajax = req.getHeader("ajax");
        if(StringUtils.isNotBlank(referer)  && StringUtils.isNotBlank(ajax) && ajax.equals("1")){
            res.setCharacterEncoding("UTF-8");
            res.setContentType("application/json; charset=utf-8");
            if(e instanceof BusinessException){
                List<FieldError> fieldErrors = ((BusinessException) e).getFieldErrors();
                if(CollectionUtils.isNotEmpty(fieldErrors)){
                    Result result = new Result(-1, e.getLocalizedMessage());
                    Map<String,Object> map = new HashMap<>();

                    fieldErrors.forEach(fieldError -> {
                        map.put(fieldError.getField(),fieldError.getDefaultMessage());
                    });
                    map.put("common",e.getLocalizedMessage());

                    result.setMessage(map);

                    res.getWriter().write(JSONObject.fromObject(result).toString());
                    return null;
                }
            }
            Result result = new Result(-1, e.getLocalizedMessage());
            result.setData(e);
            res.getWriter().write(JSONObject.fromObject(result).toString());
            return null;
        }


        //仅处理自定义异常即net.toocruel.iqismart.web.exception包下的异常,不包含400 404 500等异常
        if(e instanceof SessionInvalidException){
             return "error/sessionInvalid";
        }

        if(e instanceof NotFoundException){
            return "error/404";
        }

        if(e  instanceof AccessDeniedException){
            return "error/"+403;
        }

        e.printStackTrace();
        req.setAttribute("error",e);
        //默认情况下未处理的异常会转给500页面
        return "error/"+500;
    }

//    /**
//     * 参数校验类异常处理
//     *
//     * @param req
//     * @param e
//     * @return
//     * @throws Exception
//     */
//    @ExceptionHandler(value = BindException.class)
//    public String bindExceptionHandler(HttpServletRequest req, HttpServletResponse res, Exception e,RedirectAttributes redirectAttributes) throws Exception {
//        if(e instanceof BindException){
//            //参数校验异常 返回到表单页 并带上错误信息
//            redirectAttributes.addFlashAttribute("errors", ((BindException) e).getAllErrors());
//            req.getParameterMap().forEach((k,v)->{
//                if(v instanceof String[] && v.length == 1){
//                    redirectAttributes.addFlashAttribute(k,((String[])v)[0]);
//                }else{
//                    redirectAttributes.addFlashAttribute(k,v);
//                }
//            });
//            return "redirect:"+req.getHeader("referer");
//        }
//        //默认情况下未处理的异常会转给500页面
//        e.printStackTrace();
//        return "error/"+500;
//    }
}
